package com.szewec.ps.util.ossservice;

import com.alibaba.sdk.android.oss.ClientException;
import com.alibaba.sdk.android.oss.OSS;
import com.alibaba.sdk.android.oss.ServiceException;
import com.alibaba.sdk.android.oss.callback.OSSCompletedCallback;
import com.alibaba.sdk.android.oss.internal.OSSAsyncTask;
import com.alibaba.sdk.android.oss.model.CompleteMultipartUploadResult;
import com.alibaba.sdk.android.oss.model.MultipartUploadRequest;
import com.alibaba.sdk.android.oss.model.ObjectMetadata;
import com.szewec.ps.greenDao.dao.AlbumFile;
import com.szewec.ps.model.UserInfo;
import com.szewec.ps.util.BitmapFileSetting;
import com.szewec.ps.util.CommonUtils;
import com.szewec.ps.util.Constants;
import com.szewec.ps.util.DateUtil;
import com.szewec.ps.util.GsonUtil;
import com.szewec.ps.util.PreferincesContext;
import com.szewec.ps.util.SharedPreferencesUtil;
import com.szewec.ps.util.imagepicker.data.MediaFile;
import com.szewec.ps.util.okhttp.OkHttp;

import java.io.IOException;
import java.util.HashMap;

import okhttp3.Response;

/**
 * oss上传下载工具,因为token会变,所以oss实例化在使用时请求接口获取
 */
public class OssService {
    private static OSS mOss;
    private static String bucketName;
    private static UserInfo userInfo;

    //使用构造方法，完成初始化
    public OssService(OSS oss, String bucket) {
        this.mOss = oss;
        this.bucketName = bucket;
        String info = (String) SharedPreferencesUtil.getData(PreferincesContext.USER_INFO, "");
        this.userInfo = GsonUtil.GsonToBean(info, UserInfo.class);
    }

    public interface UploadCallBack {
        void onSuccess(String result);

        void onFailure();
    }

    public interface FirstFrameCallBack {
        void onSuccess(CompleteMultipartUploadResult result);
    }

    /**
     * 上传附件（离线）
     *
     * @param albumFile
     * @param callBack
     */
    public void upload(AlbumFile albumFile, UploadCallBack callBack) {
        String objKey = Constants.FOLDER_NAME + DateUtil.getCurDateInString("yyyyMMdd") + "_" + albumFile.getId() + "_" + albumFile.getFileName();
        String fileType = albumFile.getFileType().toLowerCase();
        if (".mp4".equals(fileType) || ".mkv".equals(fileType) || ".wmv".equals(fileType) || ".avi".equals(fileType)) {
            //如果该附件是视频， 需要先上传视频的第一帧作为视频预览时的缩略图
            String path = BitmapFileSetting.getLocalVideoBitmap(albumFile.getPath());//获取视频第一帧
            if (path == null) {//如果视频截取不了第一帧， 则直接上传视频
                callMultipartUploadRequest(objKey, null, albumFile, callBack);
            } else {
                this.uploadFirstFrame(Constants.FOLDER_NAME + DateUtil.getCurDateInString("yyyyMMdd") + "_" + albumFile.getId() + "_" + Constants.FIRST_FRAME, path, new FirstFrameCallBack() {
                    @Override
                    public void onSuccess(CompleteMultipartUploadResult result) {
                        String videoFirstImgKey = result.getLocation();
                        callMultipartUploadRequest(objKey, videoFirstImgKey, albumFile, callBack);
                    }
                });
            }
        } else {
            callMultipartUploadRequest(objKey, null, albumFile, callBack);
        }
    }

    /**
     * 上传附件（有线）
     *
     * @param mediaFile
     * @param callBack
     */
    public void upload(MediaFile mediaFile, UploadCallBack callBack) {
        String objKey = Constants.FOLDER_NAME + DateUtil.getCurDateInString("yyyyMMdd") + "_" + CommonUtils.generateId() + "_" + mediaFile.getFileName();
        String fileType = mediaFile.getFileType().toLowerCase();
        if (".mp4".equals(fileType) || ".mkv".equals(fileType) || ".wmv".equals(fileType) || ".avi".equals(fileType)) {
            //如果该附件是视频， 需要先上传视频的第一帧作为视频预览时的缩略图
            String path = BitmapFileSetting.getLocalVideoBitmap(mediaFile.getPath());//获取视频第一帧
            if (path == null) {//如果视频截取不了第一帧， 则直接上传视频
                callMultipartUploadRequest(objKey, null, mediaFile, callBack);
            } else {
                this.uploadFirstFrame(Constants.FOLDER_NAME + DateUtil.getCurDateInString("yyyyMMdd") + "_" + CommonUtils.generateId() + "_" + Constants.FIRST_FRAME, path, new FirstFrameCallBack() {
                    @Override
                    public void onSuccess(CompleteMultipartUploadResult result) {
                        String videoFirstImgKey = result.getLocation();
                        callMultipartUploadRequest(objKey, videoFirstImgKey, mediaFile, callBack);
                    }
                });
            }
        } else {
            callMultipartUploadRequest(objKey, null, mediaFile, callBack);
        }
    }


    /**
     * 专门用来上传视频的第一帧
     *
     * @param objKey
     * @param path
     */
    private void uploadFirstFrame(String objKey, String path, FirstFrameCallBack callBack) {
        MultipartUploadRequest request = new MultipartUploadRequest(bucketName, objKey, path);
        ObjectMetadata metadata = new ObjectMetadata();
        metadata.setHeader("x-oss-object-acl", "public-read");
        request.setMetadata(metadata);
        OSSAsyncTask task = mOss.asyncMultipartUpload(request, new OSSCompletedCallback<MultipartUploadRequest, CompleteMultipartUploadResult>() {
            @Override
            public void onSuccess(MultipartUploadRequest request, CompleteMultipartUploadResult result) {
                callBack.onSuccess(result);
            }

            @Override
            public void onFailure(MultipartUploadRequest request, ClientException clientException, ServiceException serviceException) {

            }
        });
        task.waitUntilFinished();
    }


    /**
     * 调OSS分片上传的接口（离线接口）
     *
     * @param objKey
     * @param videoFirstImgKey
     * @param albumFile
     * @param callBack
     */
    private void callMultipartUploadRequest(String objKey, String videoFirstImgKey, AlbumFile albumFile, UploadCallBack callBack) {
        String path = albumFile.getPath();
        try {
            //兼容三星,小米手机照片上传时旋转问题并同时进行图片压缩,返回不为空,则是图片文件
            path = BitmapFileSetting.settingFileDegreeToNewFilePath(path);
        } catch (IOException e) {
            e.printStackTrace();
        }
        MultipartUploadRequest request = new MultipartUploadRequest(bucketName, objKey, path);
        ObjectMetadata metadata = new ObjectMetadata();//设置请求头， 让上传的照片和视频可访问
        metadata.setHeader("x-oss-object-acl", "public-read");
        request.setMetadata(metadata);
        OSSAsyncTask task = mOss.asyncMultipartUpload(request, new OSSCompletedCallback<MultipartUploadRequest, CompleteMultipartUploadResult>() {
            @Override
            public void onSuccess(MultipartUploadRequest request, CompleteMultipartUploadResult result) {
                //上传基础数据到勘察服务器
                HashMap<String, Object> paramsComment = new HashMap<>();
                paramsComment.put("description", "");
                paramsComment.put("type", Integer.valueOf(albumFile.getCommentType()));
                HashMap<String, Object> params = new HashMap<>();
                params.put("id", albumFile.getId());
                params.put("bizId", albumFile.getBizId());
                params.put("bizType", albumFile.getBizType());
                params.put("comment", GsonUtil.beanToString(paramsComment));//此处的CommentType经过处理
                params.put("convertStatus", 1);
                params.put("converterPdfKey", null);
                params.put("createTime", DateUtil.getCurTimeInLong());
                params.put("createUserId", userInfo.getId());
                params.put("createUserName", userInfo.getName());
                params.put("fileKey", result.getObjectKey());
                params.put("fileLatitude", albumFile.getLatitude());
                params.put("fileLongitude", albumFile.getLongitude());
                params.put("name", albumFile.getFileName());
                params.put("path", result.getLocation());
                params.put("resizeFileKey", null);
                params.put("size", request.getPartSize());
                params.put("type", albumFile.getFileType());
                params.put("videoFirstImgKey", videoFirstImgKey);
                params.put("videoPath", null);
                String fileType = albumFile.getFileType();
                if (".mp4".equals(fileType) || ".mkv".equals(fileType) || ".wmv".equals(fileType) || ".avi".equals(fileType)) {
                    params.put("videoPath", result.getLocation());
                }
                OkHttp.post("/pmms-file-service/api/file", params, (fileResult -> {
                    callBack.onSuccess(fileResult);
                }));
            }

            @Override
            public void onFailure(MultipartUploadRequest request, ClientException clientException, ServiceException serviceException) {
                serviceException.toString();
                callBack.onFailure();
            }
        });
        task.waitUntilFinished();
    }

    /**
     * 调OSS分片上传的接口（有线接口）
     *
     * @param objKey
     * @param videoFirstImgKey
     * @param mediaFile
     * @param callBack
     */
    private void callMultipartUploadRequest(String objKey, String videoFirstImgKey, MediaFile mediaFile, UploadCallBack callBack) {
        String path = mediaFile.getPath();
        try {
            //兼容三星,小米手机照片上传时旋转问题并同时进行图片压缩,返回不为空,则是图片文件
            path = BitmapFileSetting.settingFileDegreeToNewFilePath(path);
        } catch (IOException e) {
            e.printStackTrace();
        }
        MultipartUploadRequest request = new MultipartUploadRequest(bucketName, objKey, path);
        ObjectMetadata metadata = new ObjectMetadata();//设置请求头， 让上传的照片和视频可访问
        metadata.setHeader("x-oss-object-acl", "public-read");
        request.setMetadata(metadata);
        OSSAsyncTask task = mOss.asyncMultipartUpload(request, new OSSCompletedCallback<MultipartUploadRequest, CompleteMultipartUploadResult>() {
            @Override
            public void onSuccess(MultipartUploadRequest request, CompleteMultipartUploadResult result) {
                //上传基础数据到规划服务器
                HashMap<String, Object> paramsComment = new HashMap<>();
                paramsComment.put("description", "");
                paramsComment.put("type", Integer.valueOf(mediaFile.getCommentType()));
                HashMap<String, Object> params = new HashMap<>();
                params.put("id", mediaFile.getId());
                params.put("bizId", mediaFile.getBizId());
                params.put("bizType", mediaFile.getBizType());
                params.put("comment", GsonUtil.beanToString(paramsComment));//此处的CommentType经过处理
                params.put("convertStatus", 1);
                // 转换PDF后文件key
//                params.put("converterPdfKey", null);
                params.put("createTime", DateUtil.getCurTimeInLong());
                params.put("createUserId", userInfo.getId());
                params.put("createUserName", userInfo.getName());
                params.put("fileKey", result.getObjectKey());
                // 文件的经纬度
//                params.put("fileLatitude", mediaFile.getLatitude());
//                params.put("fileLongitude", mediaFile.getLongitude());
                params.put("name", mediaFile.getFileName());
                params.put("path", result.getLocation());
                // 图片文件压缩后的路径
//                params.put("resizeFileKey", null);
                params.put("size", request.getPartSize());
                params.put("type", mediaFile.getFileType());
                // 视频第一帧的图片key
//                params.put("videoFirstImgKey", videoFirstImgKey);
                params.put("videoPath", null);
                String fileType = mediaFile.getFileType();
                if (".mp4".equals(fileType) || ".mkv".equals(fileType) || ".wmv".equals(fileType) || ".avi".equals(fileType)) {
                    params.put("videoPath", result.getLocation());
                }
                OkHttp.post("/tpms-file-service/api/file", params, (fileResult -> {
                    callBack.onSuccess(fileResult);
                }));
            }

            @Override
            public void onFailure(MultipartUploadRequest request, ClientException clientException, ServiceException serviceException) {
                serviceException.toString();
                callBack.onFailure();
            }
        });
        task.waitUntilFinished();
    }


    /**
     * 删除附件（有线接口）
     *
     * @param ids
     * @param callBack
     */
    public void delete(String ids, UploadCallBack callBack) {
        OkHttp.post("/pmms-file-service/api/file/actions/batch-delete?source=PMMS&ids=" + ids, new HashMap<>(), (result -> {

        }));
    }
}
